package com.cfec.educationplatform.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.cfec.educationplatform.domain.BetPraHistoryResult;
import com.cfec.educationplatform.domain.TbPraHistory;
import com.cfec.educationplatform.domain.TbPraResult;
import com.cfec.educationplatform.domain.TbPractice;
import com.cfec.educationplatform.mapper.TbPraHistoryMapper;
import com.cfec.educationplatform.mapper.TbPraResultMapper;
import com.cfec.educationplatform.mapper.TbPracticeMapper;
import com.cfec.educationplatform.service.BetPraHistoryResultService;
import com.cfec.educationplatform.mapper.BetPraHistoryResultMapper;
import com.cfec.educationplatform.util.DateFormatUtil;
import com.cfec.educationplatform.util.EnumSubjects;
import com.cfec.educationplatform.util.EnumTopicClassify;
import com.cfec.educationplatform.util.ResultData;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

/**
* @author diyu
* &#064;description  针对表【bet_pra_history_result(练习历史和练习详情的中间表)】的数据库操作Service实现
* &#064;createDate  2025-04-12 10:35:50
 */
@Slf4j
@Service
public class BetPraHistoryResultServiceImpl extends ServiceImpl<BetPraHistoryResultMapper, BetPraHistoryResult>
    implements BetPraHistoryResultService{

    private static final String TopicResult_ture  = "正确";
    private static final String TopicResult_false  = "错误";
    private static final String TopicDifficult_easy = "简单";
    private static final String TopicDifficult_medium = "中等";
    private static final String TopicDifficult_hard = "困难";

    @Resource(name = "betPraHistoryResultMapper")
    private BetPraHistoryResultMapper betPraHistoryResultMapper;

    @Resource(name = "tbPraHistoryMapper")
    private TbPraHistoryMapper tbPraHistoryMapper;

    @Resource(name = "tbPraResultMapper")
    private TbPraResultMapper tbPraResultMapper;

    @Resource(name = "tbPracticeMapper")
    private TbPracticeMapper tbPracticeMapper;

    @Autowired
    private DateFormatUtil dateFormatUtil;

    /**
     * 获取练习历史
     * @param userId 用户id
     * @return 该用户所有练习的记录
     */
    @Override
    public ResultData<Object> getHistory(Long userId) {
        try {
            ArrayList<List<TbPraHistory>> betPraHistoryResults_res = new ArrayList<>();
            QueryWrapper<BetPraHistoryResult> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("user_id", userId)
                    .eq("bet_pro_state", "1");
            List<BetPraHistoryResult> betPraHistoryResults = betPraHistoryResultMapper.selectList(queryWrapper);
            for (int i = 0; i < betPraHistoryResults.size(); i++) {
                // 获取当前BetPraHistoryResult对象的historyId值
                Long historyId = betPraHistoryResults.get(i).getHistoryId();

                // 创建一个新的QueryWrapper对象，用于构造新的查询条件
                QueryWrapper<TbPraHistory> queryWrapper1 = new QueryWrapper<>();

                // 设置查询条件，这里查询的是history_id等于historyId的记录
                queryWrapper1.eq("history_id", historyId)
                        .eq("history_state", "1");
                List<TbPraHistory> tbPraHistories = tbPraHistoryMapper.selectList(queryWrapper1);
                tbPraHistories.forEach(tbPraHistory -> {
                // 将historySubjects由数字转化为对应的枚举值
                String s = String.valueOf(tbPraHistory.getHistorySubjects());
                switch (s) {
                    //0:数学；1:物理；2:化学；3:英语
                    case "0":
                        tbPraHistory.setHistorySubjects(EnumSubjects.math.getValue());
                        break;
                    case "1":
                        tbPraHistory.setHistorySubjects(EnumSubjects.physics.getValue());
                        break;
                    case "2":
                        tbPraHistory.setHistorySubjects(EnumSubjects.chemistry.getValue());
                        break;
                    case "3":
                        tbPraHistory.setHistorySubjects(EnumSubjects.english.getValue());
                        break;
                    default:
                        break;
                }
                    String historyGrade = tbPraHistory.getHistoryGrade();
                    switch (historyGrade) {
                        case "grade1":
                            tbPraHistory.setHistoryGrade("一年级");
                            break;
                        case "grade2":
                            tbPraHistory.setHistoryGrade("二年级");
                            break;
                        case "grade3":
                            tbPraHistory.setHistoryGrade("三年级");
                            break;
                        case "grade4":
                            tbPraHistory.setHistoryGrade("四年级");
                            break;
                        case "grade5":
                            tbPraHistory.setHistoryGrade("五年级");
                            break;
                        case "grade6":
                            tbPraHistory.setHistoryGrade("六年级");
                            break;
                        case "junior1":
                            tbPraHistory.setHistoryGrade("初一");
                            break;
                        case "junior2":
                            tbPraHistory.setHistoryGrade("初二");
                            break;
                        case "junior3":
                            tbPraHistory.setHistoryGrade("初三");
                            break;
                        case "senior1":
                            tbPraHistory.setHistoryGrade("高一");
                            break;
                        case "senior2":
                            tbPraHistory.setHistoryGrade("高二");
                            break;
                        case "senior3":
                            tbPraHistory.setHistoryGrade("高三");
                            break;
                    }

                });
                // 执行查询，并将结果添加到betPraHistoryResults_res列表中
                betPraHistoryResults_res.add(tbPraHistories);
            }
            return new ResultData<>(200, "查询成功", betPraHistoryResults_res);
        } catch (Exception e) {
            return new ResultData<>(500, "查询失败", e);
        }
    }

    /**
     * 获取练习详情
     * @param userId 用户id
     * @return 本次练习的数据
     */
    @Override
    public ResultData<Object> getTopicInfo(Long userId) {
        try {
            ArrayList<TbPraResult> betPraResults_res = new ArrayList<>();
            QueryWrapper<BetPraHistoryResult> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("user_id", userId)
                    .eq("bet_pro_state", "1");
            List<BetPraHistoryResult> betPraHistoryResults = betPraHistoryResultMapper.selectList(queryWrapper);
            // 获取当前BetPraHistoryResult对象的resultId值
            List<Long> resultId_list = betPraHistoryResults.stream()
                    .map(BetPraHistoryResult::getResultId)
                    .collect(Collectors.toList());
            for (Long aLong : resultId_list) {
                QueryWrapper<TbPraResult> queryWrapper1 = new QueryWrapper<>();
                queryWrapper1.eq("result_id", aLong)
                        .eq("result_state", "1");
                TbPraResult tbPraResult = tbPraResultMapper.selectOne(queryWrapper1);
                // 将resTopicClassify由数字转化为对应的结果
                switch (tbPraResult.getResTopicClassify()){
                    case "0": // 0：选择题
                        tbPraResult.setResTopicClassify(EnumTopicClassify.choice.getValue());
                        break;
                    case "1": // 1：填空题
                        tbPraResult.setResTopicClassify(EnumTopicClassify.fill.getValue());
                        break;
                    case "2": // 2：计算题
                        tbPraResult.setResTopicClassify(EnumTopicClassify.calculate.getValue());
                        break;
                    case "3":// 3：简答题
                        tbPraResult.setResTopicClassify(EnumTopicClassify.shortAnswer.getValue());
                        break;
                    default:
                        break;
                }

                // 将resultTopic由数字转化为对应的结果
                switch (tbPraResult.getResultTopic()) {
                    case "0":
                        tbPraResult.setResultTopic(TopicResult_ture);
                        break;
                    case "1":
                        tbPraResult.setResultTopic(TopicResult_false);
                        break;
                    default:
                        break;
                }
                betPraResults_res.add(tbPraResult);
            }
            return new ResultData<>(200, "查询成功", betPraResults_res);

        }catch (Exception e){
            return new ResultData<>(500, "查询失败", e);
        }
    }



    /**
     * 获取错题
     * @param userId 用户id
     * @return 所有错题记录
     */
    @Override
    public ResultData<Object> getErrAll(Long userId) {
        try {
            ArrayList<Object> results_list = getErrList(userId);

            return new ResultData<>(200, "查询成功", results_list);
        }catch (Exception e){
//            throw new RuntimeException(e);
            return new ResultData<>(500, "查询失败", e.getMessage());
        }
    }



    /**
     * 删除错题
     * @param userId 用户id
     * @param resultId 错题id
     * @return 删除结果
     */
    @Override
    public ResultData<Object> deleteErrByID(Long userId, Long resultId) {
        try {
            QueryWrapper<BetPraHistoryResult> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("user_id", userId)
                    .eq("bet_pro_state", "1");
            List<BetPraHistoryResult> betPraHistoryResults = betPraHistoryResultMapper.selectList(queryWrapper);
            for (BetPraHistoryResult betPraHistoryResult : betPraHistoryResults) {
                Long currentResultId = betPraHistoryResult.getResultId();
                if (!currentResultId.equals(resultId)) {
                    log.error("未找到result_id={}的错误题目记录或题目信息为空", resultId);
                    continue;
                }
                QueryWrapper<TbPraResult> queryWrapper1 = new QueryWrapper<>();
                queryWrapper1.eq("result_id", currentResultId)
                        .eq("result_state", "1");
                TbPraResult tbPraResult = tbPraResultMapper.selectOne(queryWrapper1);
                tbPraResult.setResultState("0");
                tbPraResultMapper.update(tbPraResult, queryWrapper1);
                return new ResultData<>(200, "删除成功",null);
            }
            return new ResultData<>(500, "删除失败", null);

        }catch (Exception e) {
            return new ResultData<>(500, "删除失败", e.getMessage());
        }
    }

    /**
     * 按科目分类获取错题集
     * @param userId 用户id
     * @return 所有错题记录(以科目分类的方式)
     */
    @Override
    public ResultData<Object> getErrByClassify(Long userId) {
        try {
            HashMap<Object, Object> res_ErrMap = new HashMap<>();
            ArrayList<Object> errList = getErrList(userId);
            // 整理数据集
            ArrayList<Object> English_ListErr = getClassifyErr(EnumSubjects.english.getValue(), errList);
            res_ErrMap.put(EnumSubjects.english.getValue(), English_ListErr);  // 英语
            ArrayList<Object> Physics_ListErr = getClassifyErr(EnumSubjects.physics.getValue(), errList);
            res_ErrMap.put(EnumSubjects.physics.getValue(), Physics_ListErr);  // 物理
            ArrayList<Object> math_ListErr = getClassifyErr(EnumSubjects.math.getValue(), errList);
            res_ErrMap.put(EnumSubjects.math.getValue(), math_ListErr);  // 数学
            ArrayList<Object> chemistry_ListErr = getClassifyErr(EnumSubjects.chemistry.getValue(), errList);
            res_ErrMap.put(EnumSubjects.chemistry.getValue(), chemistry_ListErr);  // 化学
            // 返回数据
            return new ResultData<>(200, "获取成功", res_ErrMap);
        } catch (Exception e) {
//            throw new RuntimeException(e);
            return new ResultData<>(500, "获取失败", e.getMessage());
        }
    }

    @Override
    public ResultData<Object> GetPraHistoryDetails(Long historyId) {
        try {
            ArrayList<Object> res_list = new ArrayList<>();
            QueryWrapper<BetPraHistoryResult> queryWrapper1 = new QueryWrapper<>();
            queryWrapper1.select("result_id")
                    .eq("history_id", historyId)
                    .eq("bet_pro_state", "1");
            List<Long> ResultId_list = betPraHistoryResultMapper.selectList(queryWrapper1).stream()
                    .map(BetPraHistoryResult::getResultId)
                    .collect(Collectors.toList());
            for (Long aLong : ResultId_list) {
                QueryWrapper<TbPraResult> queryWrapper = new QueryWrapper<>();
                queryWrapper.eq("result_id", aLong)
                        .eq("result_state", "1");
                TbPraResult tbPraResult = tbPraResultMapper.selectOne(queryWrapper);
                res_list.add(tbPraResult);
            }
            return new ResultData<>(200, "获取成功", res_list);
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }

    @Override
    public ResultData<Object> getErrBySubject(Long userId) {
        ArrayList<Object> list = new ArrayList<>();
        QueryWrapper<BetPraHistoryResult> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("user_id", userId)
                .eq("bet_pro_state", 1);
        List<BetPraHistoryResult> betPraHistoryResults = betPraHistoryResultMapper.selectList(queryWrapper);

        // 1. 获取所有 result_id 对应的错题（result_topic=0）
        List<Long> resultIds = betPraHistoryResults.stream()
                .map(BetPraHistoryResult::getResultId)
                .collect(Collectors.toList());

        QueryWrapper<TbPraResult> errorQueryWrapper = new QueryWrapper<>();
        errorQueryWrapper.in("result_id", resultIds)
                .eq("result_topic", 0)
                .eq("result_state", 1);
        List<TbPraResult> errorResults = tbPraResultMapper.selectList(errorQueryWrapper);

        // 2. 获取所有错题对应的 practice_id
        List<Integer> practiceIds = errorResults.stream()
                .map(TbPraResult::getResultId)
                .map(resultId -> {
                    QueryWrapper<BetPraHistoryResult> historyQuery = new QueryWrapper<>();
                    historyQuery.eq("result_id", resultId)
                            .eq("bet_pro_state", 1);
                    BetPraHistoryResult history = betPraHistoryResultMapper.selectOne(historyQuery);
                    return history != null ? history.getPracticeId() : null;
                })
                .filter(Objects::nonNull)
                .collect(Collectors.toList());

        // 3. 查询所有错题对应的 TbPractice
        List<TbPractice> tbPractices = practiceIds.stream()
                .map(tbPracticeMapper::selectById)
                .filter(Objects::nonNull)
                .collect(Collectors.toList());

        System.out.println("================");
        System.out.println("tbPractices: " + tbPractices);

        // 转换科目表达式
        tbPractices.forEach(this::conversionSubjects);

        // 4. 按科目分类统计
        HashMap<String, Object> mathNumber = getNumber(tbPractices, EnumSubjects.math.getValue());
        if (!mathNumber.isEmpty()) {
            list.add(mathNumber);
        }

        HashMap<String, Object> chemistryNumber = getNumber(tbPractices, EnumSubjects.chemistry.getValue());
        if (!chemistryNumber.isEmpty()) {
            list.add(chemistryNumber);
        }

        HashMap<String, Object> englishNumber = getNumber(tbPractices, EnumSubjects.english.getValue());
        if (!englishNumber.isEmpty()) {
            list.add(englishNumber);
        }

        HashMap<String, Object> physicsNumber = getNumber(tbPractices, EnumSubjects.physics.getValue());
        if (!physicsNumber.isEmpty()) {
            list.add(physicsNumber);
        }

        return new ResultData<>(200, "查询成功", list);
    }

    private void conversionSubjects(TbPractice tbPractice) {
        switch (tbPractice.getPracticeSubjects()) {
            // 0:数学；1:物理；2:化学；3:英语
            case "0":
                tbPractice.setPracticeSubjects(EnumSubjects.math.getValue());
                break;
            case "1":
                tbPractice.setPracticeSubjects(EnumSubjects.physics.getValue());
                break;
            case "2":
                tbPractice.setPracticeSubjects(EnumSubjects.chemistry.getValue());
                break;
            case "3":
                tbPractice.setPracticeSubjects(EnumSubjects.english.getValue());

        }
    }

    public HashMap<String, Object> getNumber(List<TbPractice> ResultTopics, String subject) {
        HashMap<String, Object> numberHashMap = new HashMap<>();
        int count = 0; // 统计当前长度的用户数量


        for (TbPractice ResultTopic : ResultTopics) {
            String userAccount = ResultTopic.getPracticeSubjects();
            if (userAccount.equals(subject)) {
                count++;
            }
        }

        if (count > 0) { // 只有匹配到用户才返回数据
            numberHashMap.put("classify", subject);
            numberHashMap.put("Number", count);
        }

        return numberHashMap;
    }

    private ArrayList<Object> getErrList(Long userId) {
        ArrayList<Object> results_list = new ArrayList<>();
        HashMap<Object, Object> currMap = new HashMap<>();
        QueryWrapper<BetPraHistoryResult> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("user_id", userId)
                .eq("bet_pro_state", "1");
        List<Long> ResultId_list = betPraHistoryResultMapper.selectList(queryWrapper).stream()
                .map(BetPraHistoryResult::getResultId)
                .collect(Collectors.toList());
        for (Long aLong : ResultId_list) {
            QueryWrapper<TbPraResult> queryWrapper1 = new QueryWrapper<>();
            queryWrapper1.eq("result_id", aLong)
                    .eq("result_topic", "0")
                    .eq("result_state", "1");
            TbPraResult tbPraResult = tbPraResultMapper.selectOne(queryWrapper1);
            log.info("tbPraResult:{}", tbPraResult);
            if (tbPraResult == null) {
                log.warn("未找到result_id={}的错误题目记录或题目信息为空", aLong);
                continue;
            }
            currMap.put("result_id", tbPraResult.getResultId());
            QueryWrapper<TbPractice> queryWrapper2 = new QueryWrapper<>();
            queryWrapper2.eq("practice_info", tbPraResult.getResTopicInfo())
                    .eq("practice_state", "1");
            TbPractice tbPractice = tbPracticeMapper.selectOne(queryWrapper2);
            // 科目:0:数学；1:物理；2:化学；3:英语
            conversionSubjects(tbPractice);

            switch (tbPractice.getPracticeClassify()) {
                // 0：选择题；1：填空题；2：计算题；3：简答题
                case "0":
                    tbPractice.setPracticeClassify(EnumTopicClassify.choice.getValue());
                    break;
                case "1":
                    tbPractice.setPracticeClassify(EnumTopicClassify.fill.getValue());
                    break;
                case "2":
                    tbPractice.setPracticeClassify(EnumTopicClassify.calculate.getValue());
                    break;
                case "3":
                    tbPractice.setPracticeClassify(EnumTopicClassify.shortAnswer.getValue());
                default:
                    break;
            }

            switch (tbPractice.getPracticeDifficult()) {
                // 难度：0：简单；1：中等；2：困难
                case "0":
                    tbPractice.setPracticeDifficult(TopicDifficult_easy);
                    break;
                case "1":
                    tbPractice.setPracticeDifficult(TopicDifficult_medium);
                    break;
                case "2":
                    tbPractice.setPracticeDifficult(TopicDifficult_hard);
                    break;
                default:
                    break;
            }
            currMap.put("practiceSubjects", tbPractice.getPracticeSubjects());
            currMap.put("practiceClassify", tbPractice.getPracticeClassify());
            currMap.put("practiceInfo",tbPractice.getPracticeInfo());
            currMap.put("practiceDifficult", tbPractice.getPracticeDifficult());
            currMap.put("practiceParse",tbPractice.getPracticeParse());
            currMap.put("practiceAnswer", tbPractice.getPracticeAnswer());
            currMap.put("date", dateFormatUtil.getCreateTimeFormatted(tbPractice.getCreateTime()));
            results_list.add(new HashMap<>(currMap));
        }
        return results_list;
    }

    private static ArrayList<Object> getClassifyErr(String classify,ArrayList<Object> errList) {
        ArrayList<Object> res_list = new ArrayList<>();
        errList.stream()
                .filter(item -> item instanceof Map)  // 过滤流中的元素，只保留 Map 类型的对象
                .map(item -> (Map<?, ?>) item)  // 将过滤后的元素转换为 Map 类型
                .forEach(resMap -> {  // 遍历 Map 类型的对象
                    resMap.forEach((key, value) -> {  // 遍历 Map 的键值对
                        log.info("Key: {}, Value: {}", key, value);
                        if (value.toString().equals(classify)){
                            res_list.add(resMap);
                        }
                    });
                });
        return res_list;
    }
}




